package cn.rui.controller;

import cn.rui.aop.Log;
import cn.rui.pojo.Admins;
import cn.rui.service.AdminService;
import cn.rui.utils.IpUtils;
import cn.rui.utils.Result;
import cn.rui.vo.PermAdminQuery;
import org.apache.ibatis.annotations.Options;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.IncorrectCredentialsException;
import org.apache.shiro.authc.UnknownAccountException;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.authz.annotation.Logical;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.apache.shiro.authz.annotation.RequiresRoles;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @author 徽州大都督
 * @date 2020/8/12
 */
@RestController
@RequestMapping("admin")
public class AdminController {

    @Autowired
    private AdminService adminService;

    @Autowired
    private RedisTemplate redisTemplate;

    /**
     * 管理员添加
     *
     * @param admins
     * @return
     */
    @Log("管理员添加")
    @PostMapping("addAdmin")
    public String addAdmin(@RequestBody Admins admins) {

        System.out.println (admins);
        int register = adminService.register (admins);
        if (register > 0) {
            return "success";
        } else {
            return "error";
        }

    }

    /**
     * 登陆方法
     *
     * @param adminUsername
     * @param adminPassword
     * @return
     */
    @Log("管理员登陆")
    @PostMapping("login/{adminUsername}/{adminPassword}/{code}")
    public Result login(@PathVariable("adminUsername") String adminUsername, @PathVariable("adminPassword") String adminPassword,@PathVariable("code")String code, HttpServletRequest request) {



        Result result = new Result ();
        //System.out.println (code);
        String checkCode= (String) redisTemplate.opsForValue ().get ("code");
        //System.out.println (checkCode);

        if (!checkCode.equalsIgnoreCase (code)){
            result.setCode ("codeError");
            return result;
        }


        //获取主体对象
        Subject subject = SecurityUtils.getSubject ();


        try {
            subject.login (new UsernamePasswordToken (adminUsername, adminPassword));

            result.setCode ("success");
            //登陆成功修改登陆次数和登陆时间并将当前用户存于缓存

            redisTemplate.opsForValue ().set ("admin_name", adminUsername, 30, TimeUnit.DAYS);

            Admins admins = adminService.updateCounts (adminUsername);

            //认证通过判断账户状态
            if (admins.getAStatus () == 0) {
                result.setCode ("statusError");
                return result;
            }

            admins.setIp (IpUtils.getIpAddr (request));
            admins.setPer (Arrays.asList (admins.getPerStr ()));
            result.setAdmins (admins);
            return result;
        } catch (UnknownAccountException e) {

            result.setCode ("nameError");
            return result;
        } catch (IncorrectCredentialsException e) {

            //密码错误
            redisTemplate.opsForValue ().set ("adminUsername", adminUsername);
            result.setCode ("wordError");
            return result;
        }


    }

    /**
     * 退出登陆
     */
    @Log("管理员退出登陆")
    @GetMapping("logout")
    public void logout() {

        //清除缓存
        redisTemplate.delete ("admin_name");

        //退出
        SecurityUtils.getSubject ().logout ();
    }



    /**
     * 分页查询
     *
     * @return
     */
    //@Log("管理员列表")
    @PostMapping("findByPage/{page}/{size}")
    //@Cacheable(value="admins", key="#page")
    //@Options(flushCache = Options.FlushCachePolicy.TRUE)
    public List<Admins> findByPage(@PathVariable("page") int page, @PathVariable("size") int size, @RequestBody PermAdminQuery permAdminQuery) {
        {

            return adminService.findByPage (page, size, permAdminQuery);


        }

    }

    /**
     * 启用/封禁管理员账户
     *
     * @param aid
     */
    @Log("启用/封禁管理员")
    @PutMapping("updateStatus/{aid}")
    public void updateStatus(@PathVariable("aid") Integer aid) {

        adminService.updateStatus (aid);
    }

    @Log("查看个人信息")
    @GetMapping("findByName/{username}")
    public Admins findByName(@PathVariable("username") String username) {
        return adminService.findByName (username);
    }

    /**
     * 删除管理员
     *
     * @param aid
     */
    @Log("删除管理员")
    @DeleteMapping("delAdmin/{aid}")
    public void delAdmin(@PathVariable("aid") Integer aid) {
        adminService.delAdmin (aid);
    }


    /**
     * 给管理员添加权限
     *
     * @param admin
     * @param per
     */
    @Log("管理员添加权限")
    @PostMapping("AddPerm/{admin}/{per}")
    public String addPerm(@PathVariable("admin") List<Integer> admin, @PathVariable("per") List<String> per) {
        adminService.addPerm (admin, per);

        return "success";
    }

    /**
     * 管理员修改登陆密码
     * @param username
     * @param password
     * @return
     */
    @Log("管理员修改密码")
    @PutMapping("updateAdmin/{username}/{password}")
    public void updateAdmin(@PathVariable("username") String username, @PathVariable("password") String password) {
        adminService.updateAdmin (username, password);

    }

    /**
     * 修改个人信息
     * @param username
     * @param admins
     * @return
     */
    @PostMapping("addUpdate/{username}")
    @Log("管理员修改个人信息")
    public Admins addUpdate(@PathVariable("username")String username,@RequestBody Admins admins){

        return adminService.addUpdate(username,admins);
    }
}
